<?php 
/***
    Amrita ITEWS - Copyright (C) 2009 Amrita Vishwa Vidyapeetham, Amritapuri.
                                     (http://www.amrita.edu)
    ***************************************************************************
    This file is part of the Amrita ITEWS distribution.
    Amrita ITEWS is free software; you can redistribute it and/or modify it 
    under the terms of the GNU General Public License (version 2) as published 
    by the Free Software Foundation AND MODIFIED BY the Amrita ITEWS exception.
    ***NOTE*** The exception to the GPL is included to allow you to distribute
    a combined work that includes Amrita ITEWS without being obliged to provide
    the source code for proprietary components outside of the Amrita ITEWS
    software. Amrita ITEWS is distributed in the hope that it will be useful, 
    but WITHOUT ANY WARRANTY; without even the implied warranty of 
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General
    Public License for more details. You should have received a copy of the GNU
    General Public License and the Amrita ITEWS license exception along with 
    Amrita ITEWS if not then it can be viewed here: 
    http://itews.amrita.ac.in/license.html.
    
    Documentation, latest information, license and contact details are at:
    http://itews.amrita.ac.in/
 
    Amrita ITEWS source code can be found at:
    http://code.google.com/p/itews"; 
    
    The initial code-base of Amrita ITEWS was developed by Amrita Vishwa 
    Vidyapeetham as part of the project titled,\"Intelligent & Interactive 
    Telematics using Emerging Wireless Technologies for Transport Systems 
    (ITEWS)\" sponsored by Technology Information Forecasting and Assessment 
    Council (TIFAC), India.
***/
?><?php

function download_media(){
	global $folder_structure;
	global $current_media_url;
	global $media_cache_ip_port;
	global $last_check_ts;
	global $ts;
	global $lines;
	global $pending_lines;
	global $last_known_percentage_downloaded;
	global $previous_last_known_percentage_downloaded;
	global $last_known_data_rate;
	global $previous_last_known_data_rate;
	global $previous_is_not_found;
	global $is_not_found;
	global $last_known_status;
	global $previous_last_known_status;
	global $data_has_changed;
	global $changed_parameters_array;
	global $download_media_code;

	
	global $first_time_request_initiated;

	$cmd = "wget -P ".$folder_structure." -c --retry-connrefused --timeout=".DOWNLOAD_TIMEOUT." -t ".MAX_RETRIES." http://".$media_cache_ip_port."/".$current_media_url." 2>&1";


	trigger_error("Executing -> [".$cmd."]",E_USER_NOTICE);

	trigger_error("Trying to Downloading Media: ".$download_media_code." (".$download_media_code.")",E_USER_NOTICE);
	
	/*
	time dd if=/dev/zero of=test.bin bs=1000000000 count=1
	RIGHT NOW WE DID IT ON AMRITAVANI.COM/HTDOCS, JUST FOR TESTING
	*/
	$fp = popen($cmd, "r");
	$last_check_ts = 0;

	$lines=array();
	$pending_lines=false;

	while($curr_line=fgets($fp))
	{
		$lines[] = $curr_line;
		$ts = time();
		$pending_lines=true;
		if( ($ts - $last_check_ts) > CHECK_THRESHOLD_SECS)
		{

			check_status();
			if ($data_has_changed[$download_media_code]){
				if (BEEP_ENABLED)
					//echo CURRENTLY_DOWNLOADING_BEEP;
					exec(CURRENTLY_DOWNLOADING_BEEP);
				update_db();
			}
			$pending_lines = false;
			$last_check_ts = $ts;
		}	
	}
	if($pending_lines)
	{
		check_status();
		if ($data_has_changed[$download_media_code]){

			update_db();
		}
	}
	
	if ($last_known_status[$download_media_code]=="init")
	{
		$last_known_status[$download_media_code]="unspecified";
		if ($last_known_status[$download_media_code] != $previous_last_known_status[$download_media_code]){
			$data_has_changed[$download_media_code] = true;
			if (!in_array("last_known_status", $changed_parameters_array))
				array_push($changed_parameters_array,"last_known_status");
		}
		if ($data_has_changed[$download_media_code]){

			update_db();
		}
	}

}
function check_status()
{
	global $lines;
	global $curr_line;
	global $last_check_ts;
	global $ts;
	global $last_known_percentage_downloaded;
	global $previous_last_known_percentage_downloaded;
	global $last_known_data_rate;
	global $previous_last_known_data_rate;
	global $is_not_found;
	global $previous_is_not_found;
	global $last_known_status;
	global $previous_last_known_status;
	global $data_has_changed;
	global $changed_parameters_array;
	global $download_media_code;
	global $first_time_request_initiated;


	$len = count($lines);
	for($i=$len-1;$i >= 0; $i--)
	{
		$line = $lines[$i];
		$percent_pos = strpos($line,"%");
		$not_found_pos = strpos($line,"ERROR 404");
		$fully_retrieved = strpos($line,"fully retrieved");
		$resolving_error = ereg("(Resolving)([a-zA-Z. :0-9]*)(failed:)([a-zA-Z. :0-9]*)", $line, $reserr);
		$connection_error = ereg("(Connecting)([a-zA-Z. :0-9]*)(failed:)([a-zA-Z. :0-9]*)", $line, $conerr);
		//$connection_reset = strpos($line,"Connection reset by peer");

		//if($percent_pos===FALSE && $not_found_pos===FALSE && $fully_retrieved===FALSE && $unknown_host===FALSE && $connection_reset===FALSE )
		if($percent_pos===FALSE && $not_found_pos===FALSE && $fully_retrieved===FALSE && !$resolving_error && !$connection_error )
			continue;
		
		if(!$percent_pos===FALSE )
		{
			if (ereg ("([0-9]{1,3})(\%)", $line, $regs)) {
			    $last_known_percentage_downloaded[$download_media_code] = $regs[1];
				if (ereg ("([0-9]*\.*[0-9]* [a-zA-Z]*/[sS])$", trim($line), $regs2)){
					$previous_last_known_data_rate[$download_media_code] = $last_known_data_rate[$download_media_code];
					$last_known_data_rate[$download_media_code] = $regs2[0];
				}
			} 
			if (strcmp($last_known_percentage_downloaded[$download_media_code],"100")==0){
				$last_known_status[$download_media_code] = "fully_downloaded";
				$logStr = "Fully downloaded";
			}
			else {
				$last_known_status[$download_media_code] = "downloading";
				$logStr = "Downloading media (".$download_media_code.") @ ".$last_known_data_rate[$download_media_code]." - "
						   . $last_known_percentage_downloaded[$download_media_code]."% completed";
			}
			trigger_error($logStr,E_USER_NOTICE);
		}
		else if(!$fully_retrieved===FALSE){
		//This case may not occur now since media_downloader magic query now only retrieves media for which download percentage is less than 100
			$last_known_percentage_downloaded[$download_media_code] = "100";
			$last_known_status[$download_media_code] = "already_downloaded";
			trigger_error("Media already fully retrieved",E_USER_NOTICE);
		}
		else if(!$not_found_pos===FALSE)
		{
			$is_not_found[$download_media_code] = 'T';
			$last_known_status[$download_media_code] = "not_found";
			trigger_error("Media not found",E_USER_NOTICE);
		}
		else if($connection_error)
		{
			$last_known_status[$download_media_code] = "connection_error";
			trigger_error($conerr[0],E_USER_NOTICE);
			if (BEEP_ENABLED)
				//echo NETWORK_ERROR_BEEP;
				exec(NETWORK_ERROR_BEEP);
			SLEEP(1);
			//break;
		}
		else if($resolving_error)
		{
			$last_known_status[$download_media_code] = "resolving_error";
			trigger_error($reserr[0],E_USER_NOTICE);
			if (BEEP_ENABLED)
				//echo NETWORK_ERROR_BEEP;
				exec(NETWORK_ERROR_BEEP);
			SLEEP(1);
			//break;
		}
		
		update_curr_download_status();
		
		if (isset($last_known_percentage_downloaded[$download_media_code]) && isset($previous_last_known_percentage_downloaded[$download_media_code]) && strcmp($last_known_percentage_downloaded[$download_media_code],$previous_last_known_percentage_downloaded[$download_media_code])!=0){
			$data_has_changed[$download_media_code] = true;
			if (!in_array("percentage_downloaded", $changed_parameters_array))
				$changed_parameters_array[] = "percentage_downloaded";
		}
		else{
			if (in_array("percentage_downloaded", $changed_parameters_array)){
				foreach($changed_parameters_array as $k=>$v) {
					if(strcmp($v,"percentage_downloaded")==0)
						unset($changed_parameters_array[$k]);
				}
			}
		}
		
		if (isset($last_known_data_rate[$download_media_code]) && isset($previous_last_known_data_rate[$download_media_code]) && $last_known_data_rate[$download_media_code] != $previous_last_known_data_rate[$download_media_code]){
			$data_has_changed[$download_media_code] = true;
			if (!in_array("data_rate", $changed_parameters_array))
				$changed_parameters_array[] = "data_rate";
		}
		else{
			if (in_array("data_rate", $changed_parameters_array)){
				foreach($changed_parameters_array as $k=>$v) {
					if(strcmp($v,"data_rate")==0)
						unset($changed_parameters_array[$k]);
				}
			}
		}
		
		if (isset($is_not_found[$download_media_code]) && isset($previous_is_not_found[$download_media_code]) && $is_not_found[$download_media_code] != $previous_is_not_found[$download_media_code]){
			$data_has_changed[$download_media_code] = true;
			if (!in_array("is_not_found", $changed_parameters_array))
				$changed_parameters_array[] = "is_not_found";
		}
		else {
			if (in_array("is_not_found", $changed_parameters_array)){
				foreach($changed_parameters_array as $k=>$v) {
					if(strcmp($v,"is_not_found")==0)
						unset($changed_parameters_array[$k]);
				}
			}
		}
		
		if (isset($last_known_status[$download_media_code]) && isset($previous_last_known_status[$download_media_code]) && $last_known_status[$download_media_code] != $previous_last_known_status[$download_media_code]){
			$data_has_changed[$download_media_code] = true;
			if (!in_array("last_known_status", $changed_parameters_array))
				$changed_parameters_array[] = "last_known_status";
		}
		else {
			if (in_array("last_known_status", $changed_parameters_array)){
				foreach($changed_parameters_array as $k=>$v) {
					if(strcmp($v,"last_known_status")==0)
						unset($changed_parameters_array[$k]);
				}
			}
		}
	
		if (strcmp($previous_last_known_percentage_downloaded[$download_media_code],0)==0)
			$first_time_request_initiated =true;
		else 
			$first_time_request_initiated =false;
			
		$previous_last_known_percentage_downloaded[$download_media_code] = $last_known_percentage_downloaded[$download_media_code];
		$previous_is_not_found[$download_media_code] = $is_not_found[$download_media_code];
		$previous_last_known_status[$download_media_code] = $last_known_status[$download_media_code];
		break;
	}
	$lines = null;
	$last_check_ts = $ts;
}

function update_db(){
	global $last_known_percentage_downloaded;
	global $last_known_data_rate;
	global $is_not_found;
	global $last_known_status;
	global $current_media_url;
	global $download_media_code;
	global $download_media_title;
	global $download_media_relative_media_path;
	//global $download_route_schedule_code;
	//global $download_route_schedule_desc;
	//global $download_is_for_current_route;
	global $download_percentage_downloaded;
	global $download_is_not_found;
	global $data_has_changed;
	global $changed_parameters_array;
	global $first_time_request_initiated;
	
	global $link;
	$absolute_path = MEDIA_FILE_ROOT_FOLDER."/".$current_media_url;
	$sql = 'Update media_descriptors set absolute_media_path = \''.$absolute_path.'\', percentage_downloaded = '
			. $last_known_percentage_downloaded[$download_media_code].', data_rate = \''.$last_known_data_rate[$download_media_code].'\', is_not_found =\''	. $is_not_found[$download_media_code]
			.'\', last_known_status=\''.$last_known_status[$download_media_code].'\' '
			.', time_request_was_last_processed=NOW()';
	
	if ($first_time_request_initiated)
		$sql .= ', time_request_was_initiated=NOW() ';
	
	$sql .= ' where media_code = \''.$download_media_code.'\'';

	while ( ($result = query_wrapper($sql, __FILE__, __LINE__))==null){
		sleep(III_SLEEP_TIME);
		continue;
	}
	
	$params = implode(",", $changed_parameters_array);
	
	$sql = 'INSERT INTO media_download_log (media_code, percentage_downloaded, ';	

	if (in_array("data_rate", $changed_parameters_array)){
		$sql .= ' data_rate, ';
	}
	
	$sql .= ' is_not_found, last_known_status, changed_parameters, logtime) '
			.' VALUES (\''.$download_media_code.'\', '.$last_known_percentage_downloaded[$download_media_code].', ';
			
	if (in_array("data_rate", $changed_parameters_array)){
		$sql .= '\''.$last_known_data_rate[$download_media_code].'\', ';
	}

	$sql .= ' \''.$is_not_found[$download_media_code].'\', \''.$last_known_status[$download_media_code].'\', \''.$params.'\', NOW());';

	$data_has_changed[$download_media_code] = false;

	while ( ($result = query_wrapper($sql, __FILE__, __LINE__))==null){
		sleep(III_SLEEP_TIME);
		continue;
	}
}

function update_curr_download_status(){

	global $last_known_status;
	global $download_media_code;
	
	global $link;

	$sql = 'Update curr_download_status set download_status = \''.$last_known_status[$download_media_code].'\', logtime=NOW()';
	
	$result = query_wrapper($sql, __FILE__, __LINE__);
}
?>
